package name.marz.to.go.ahg;

import java.io.File;
import java.io.IOException;
import java.net.URI;
import java.util.logging.Logger;

import name.marz.to.go.ahg.common.cli.OutFileOption;
import name.marz.to.go.ahg.common.cli.PasswordOption;
import name.marz.to.go.ahg.common.util.HttpUtil;
import name.marz.to.go.ahg.core.AbstractAutoGetterMain;
import name.marz.to.go.ahg.core.exception.UnknownClientException;
import name.marz.to.go.ahg.core.exception.UserProcessException;
import name.marz.to.go.ahg.core.executer.DocumentGetExecuter;
import name.marz.to.go.ahg.core.executer.Executer;
import name.marz.to.go.ahg.sonybank.SonyBankClient;
import name.marz.to.go.ahg.sonybank.executer.AnnouncementExecuter;
import name.marz.to.go.ahg.sonybank.executer.DealHistoryExecuter;
import name.marz.to.go.ahg.sonybank.executer.DownloadExecuter;
import name.marz.to.go.ahg.sonybank.executer.LastDealCheckExecuter;
import name.marz.to.go.ahg.sonybank.executer.LogoutExecuter;
import name.marz.to.go.ahg.sonybank.executer.SonyBankLoginExecuter;
import name.marz.to.go.ahg.sonybank.executer.TransferToAccountPageExecuter;

import org.apache.commons.cli.CommandLine;
import org.apache.commons.cli.OptionBuilder;
import org.apache.commons.cli.Options;
import org.apache.http.client.ClientProtocolException;
import org.jsoup.nodes.Document;

public class SonyBankAccountGetMain extends AbstractAutoGetterMain {
	private static final Logger log = Logger.getLogger(SonyBankAccountGetMain.class.getName());
	private static final String DEFAULT_MEISAI_FILENAME="YenFutsuRireki.csv";
	SonyBankClient client = new SonyBankClient();
	
	private String tenNo;
	private String kozaNo;
	private String password;
	private File outFile;
	
	private String cid;
	private String tid;
	private String zid;

	private String baseHost = "https://o2o.moneykit.net";
	/**
	 * 
	 */
	public SonyBankAccountGetMain() {
	}

	/**
	 * @param args
	 */
	public static void main(String[] args) {
		SonyBankAccountGetMain main = new SonyBankAccountGetMain();
		main.Main(args);
	}
	
	private void doEntryClientSequence(Document document) throws ClientProtocolException, IOException, UserProcessException {
		// TODO:端末登録処理
		log.severe("端末登録処理は未実装ですm(_ _)m");
		throw new IllegalStateException("端末登録処理は未実装です");
//		EntryClientBatchExecuter exe = new EntryClientBatchExecuter(client,context,document);
//		exe.execute();
	}

	@Override
	public Document goTopPage() throws ClientProtocolException, IOException,
			UserProcessException {
		URI uri = HttpUtil.createURISafety(baseHost,"/NBG100001G01.html");
		Executer<Document> executer = new DocumentGetExecuter(uri, client);
		return executer.execute();
	}

	@Override
	public Document doLogin(Document doc) throws ClientProtocolException,
			IOException, UserProcessException {
		URI uri = HttpUtil.createURISafety(baseHost,"/TDGate1/gate/NBW000010");
		SonyBankLoginExecuter executer = new SonyBankLoginExecuter(uri, client,new String[] {tenNo,kozaNo,cid,tid,zid},password);
		try {
			doc = executer.execute();
		} catch (UnknownClientException e) {
			doEntryClientSequence(e.getDocument());
		}
		return doc;
	}

	@Override
	public Document goDownloadPage(Document doc)
			throws ClientProtocolException, IOException, UserProcessException {
		log.info("前回取引確認処理開始");
		URI uri = HttpUtil.createURISafety(baseHost,"/TDGate/gate/NBW010003/&NBP000111G01");
		LastDealCheckExecuter ldce = new LastDealCheckExecuter(uri, client, doc);
		doc = ldce.execute();
		log.info("前回取引確認処理終了 ");
		log.fine("cookie store"+client.getCookieStore());
		// ソニーバンクからのお知らせ処理
		log.info("お知らせ処理開始");
		uri = HttpUtil.createURISafety(baseHost,"/TDGate/gate/NBW010003/&NBP000140G01");
		AnnouncementExecuter ae = new AnnouncementExecuter(uri, client, doc);
		doc = ae.execute();
		log.info("お知らせ処理終了 ");
		log.fine("cookie store"+client.getCookieStore());
		// 口座トップページへの転送ページ処理
		log.info("口座トップページへの転送処理開始");
		uri = HttpUtil.createURISafety(baseHost, "/TDGate010300/gate/NBW010300/&NBPO2OTMPG01");
		TransferToAccountPageExecuter t2ape = new TransferToAccountPageExecuter(uri, client,doc);
		doc = t2ape.execute();
		log.info("口座トップページへの転送処理終了 ");
		// 取引履歴ページへの遷移処理
		log.info("取引履歴ページへの遷移開始");
		uri = HttpUtil.createURISafety(baseHost, "/TDGate/gate/NBW010003");
		DealHistoryExecuter dhe = new DealHistoryExecuter(uri, client, doc);
		doc = dhe.execute();
		log.info("取引履歴ページへの遷移終了");
		return doc;
	}

	@Override
	public File doDownload(Document doc) throws ClientProtocolException,
			IOException, UserProcessException {
		URI uri = HttpUtil.createURISafety(baseHost, "/TDGate000036/gate/NBW000036/YenFutsuRireki.csv");
		DownloadExecuter executer = new DownloadExecuter(uri, client, outFile, doc);
		return executer.execute();
	}

	@Override
	public void doLogout(Document doc) throws ClientProtocolException,
			IOException, UserProcessException {
		URI uri = HttpUtil.createURISafety(baseHost, "/TDGate2/gate/NBW000020");
		LogoutExecuter executer = new LogoutExecuter(uri, client, doc);
		executer.execute();
	}

	@Override
	protected void finish() {
		// 終了処理
		client.getConnectionManager().shutdown();
	}

	@SuppressWarnings("static-access")
	@Override
	protected Options getOptions() {
		Options options = new Options();
		options.addOption(new OutFileOption(false));
		options.addOption(OptionBuilder.hasArg(true).withArgName("nnn")
				.isRequired(true).withDescription("店番号")
				.create("ten"));
		options.addOption(OptionBuilder.hasArg(true).withArgName("account no")
				.isRequired(true).withDescription("口座番号")
				.create("account"));
		options.addOption(new PasswordOption(true));
		options.addOption(OptionBuilder.hasArg(true).withArgName("9999999999")
				.isRequired(true).withDescription("CookieId")
				.create("cid"));
		options.addOption(OptionBuilder.hasArg(true).withArgName("9")
				.isRequired(true).withDescription("TanmatsuShubt")
				.create("t"));
		options.addOption(OptionBuilder.hasArg(true).withArgName("yyyy/mm/dd hh:mm:ss")
				.isRequired(true).withDescription("ZenkaiLogonTime")
				.create("z"));
		return options;
	}

	@Override
	protected void setParams(CommandLine cmd) {
		tenNo = cmd.getOptionValue("ten");
		kozaNo = cmd.getOptionValue("account");
		password = cmd.getOptionValue("password");
		outFile = new File(cmd.getOptionValue("out", DEFAULT_MEISAI_FILENAME));
		cid = cmd.getOptionValue("cid");
		tid = cmd.getOptionValue("t");
		zid = cmd.getOptionValue("z");
	}
}
